package com.hedl.classroom.config;

import org.springframework.context.annotation.Bean;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.NoOpPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;

import javax.annotation.Resource;

/**
 * @author Big Watermelon
 * @description 安全管理配置
 * @date 2023/12/02/17:47
 */
@EnableWebSecurity
@EnableGlobalMethodSecurity(securedEnabled = true,prePostEnabled = true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    //注入进来我们自定义的密码校验
    @Resource
    private DaoAuthenticationProviderCustom daoAuthenticationProviderCustom;

    /**
     * 设置进去
     * @param auth
     * @throws Exception
     */
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.authenticationProvider(daoAuthenticationProviderCustom);
    }

    //配置用户信息服务，这个是测试使用的临时账号密码，并且是存在内存中的
    /*
    @Bean
    @Override
    public UserDetailsService userDetailsService(){
         //这里配置用户信息,这里暂时使用这种方式将用户存储在内存中
        InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
        //authorities("p1")给定不同账号不同权限
        manager.createUser(User.withUsername("zhangsan").password("123").authorities("p1").build());
        manager.createUser(User.withUsername("lisi").password("456").authorities("p2").build());
        return manager;
    }
     */

    @Bean
    public PasswordEncoder passwordEncoder(){
        //密码为明文方式
        //return NoOpPasswordEncoder.getInstance();
        return new BCryptPasswordEncoder();
    }

    //配置安全拦截机制
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                //.antMatchers("/r/**").authenticated()       //访问/r开始的请求需要认证通过
                .anyRequest().permitAll()       //其它请求全部放行
                //.antMatchers("/**").permitAll()
                .and()
                .formLogin().successForwardUrl("/login-success");      //登录成功跳转到/login-success
        http.logout().logoutUrl("/logout");
        http.csrf().disable(); //之前访问不了注册和更改密码的接口就是这里开启了CSRF保护，关闭就可以了
    }

    @Bean
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    public static void main(String[] args) {

        String password = "111111";
        PasswordEncoder passwordEncoder = new BCryptPasswordEncoder();

        //这里生成的密码每次都不一样，加盐了
        for (int i = 0; i < 5; i++) {
            //生成密码
            String encode = passwordEncoder.encode(password);
            System.out.println(encode);

            //校验密码,matches(原始密码,编译后的密码)；做对比
            boolean matches = passwordEncoder.matches(password, encode);
            System.out.println(matches);

            //错误比对
            boolean matches1 = passwordEncoder.matches("123456", "$2a$10$L4XFko8AvNMgw0ASXgaMOeNsmniNm791PzyOVLhg7stofUSKByjSi");
            System.out.println("错误比对："+matches1);
        }

    }
}
